package com.sky.aop;

import com.sky.constant.AutoFillConstant;
import com.sky.context.BaseContext;
import com.sky.enumeration.OperationType;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.Signature;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.reflect.MethodSignature;
import org.springframework.stereotype.Component;

import java.beans.PropertyDescriptor;
import java.lang.reflect.Method;
import java.time.LocalDateTime;

@Aspect
@Component
@Slf4j
public class AutoFillAspect {


    @Around("@annotation(com.sky.aop.AutoFill)")
    public Object autoFill(ProceedingJoinPoint pjp) throws Throwable {
        log.info("aop开始执行");

        //拿到方法上的注解
        try {

            Signature signature = pjp.getSignature();
            MethodSignature methodSignature = (MethodSignature) signature;
            Method method = methodSignature.getMethod();
            AutoFill autoFill = method.getAnnotation(AutoFill.class);
            OperationType value = autoFill.value();
            Object object = pjp.getArgs()[0];

            if(value==OperationType.INSERT){
                log.info("开始进行新增数据填充");
                Class<?> clazz = object.getClass();
                Method setCreateTime = clazz.getMethod(AutoFillConstant.SET_CREATE_TIME, LocalDateTime.class);
                Method setCreateUser = clazz.getMethod(AutoFillConstant.SET_CREATE_USER, Long.class);
                Method setUpdateTime = clazz.getMethod(AutoFillConstant.SET_UPDATE_TIME, LocalDateTime.class);
                Method setUpdateUser = clazz.getMethod(AutoFillConstant.SET_UPDATE_USER, Long.class);
                setCreateTime.invoke(object, LocalDateTime.now());
                setCreateUser.invoke(object, BaseContext.getCurrentId());
                setUpdateTime.invoke(object, LocalDateTime.now());
                setUpdateUser.invoke(object, BaseContext.getCurrentId());
                /*new PropertyDescriptor("createTime", clazz).getWriteMethod().invoke(object, LocalDateTime.now());
                new PropertyDescriptor("createUser", clazz).getWriteMethod().invoke(object,  BaseContext.getCurrentId());
                new PropertyDescriptor("updateTime", clazz).getWriteMethod().invoke(object, LocalDateTime.now());
                new PropertyDescriptor("updateUser", clazz).getWriteMethod().invoke(object, BaseContext.getCurrentId());
*/
            }else if (value==OperationType.UPDATE){
                log.info("开始进行修改数据填充");
                Class<?> clazz = object.getClass();
                Method setUpdateTime = clazz.getMethod(AutoFillConstant.SET_UPDATE_TIME, LocalDateTime.class);
                Method setUpdateUser = clazz.getMethod(AutoFillConstant.SET_UPDATE_USER, Long.class);
                setUpdateTime.invoke(object, LocalDateTime.now());
                setUpdateUser.invoke(object, BaseContext.getCurrentId());
                /*new PropertyDescriptor("updateTime", clazz).getWriteMethod().invoke(object, LocalDateTime.now());
                new PropertyDescriptor("updateUser", clazz).getWriteMethod().invoke(object, BaseContext.getCurrentId());
*/
            }
            Object proceed = pjp.proceed();
            return proceed;
        } catch (Throwable e) {
            log.error("AOP 自动填充失败：", e);
            throw e;
        }
    }
}
